//response listener implementation.
function TracingListener() {
	
}

TracingListener.prototype =
{
    originalListener: null,
    receivedData    : null,

    onStartRequest: function(request, context) {
    	this.receivedData = [];   // array for incoming data.
        this.originalListener.onStartRequest(request, context);
    },
    
        onDataAvailable: function(request, context, inputStream, offset, count)
    {
    	//fix for firebug error
		if (typeof Cc == "undefined") {
		var Cc = Components.classes;
		}
		if (typeof Ci == "undefined") {
        var Ci = Components.interfaces;
		}
		if (typeof CCIN == "undefined") {
		function CCIN(cName, ifaceName){
		return Cc[cName].createInstance(Ci[ifaceName]);
		}
		}
		if (typeof CCSV == "undefined") {
		function CCSV(cName, ifaceName){
		if (Cc[cName])
			// if fbs fails to load, the error can be _CC[cName] has no properties
			return Cc[cName].getService(Ci[ifaceName]);
		else
			dumpError("CCSV fails for cName:" + cName);
		}
		}
    	//alert("AVAILABLE "+request.requestMethod);
        var binaryInputStream = CCIN("@mozilla.org/binaryinputstream;1",
                "nsIBinaryInputStream");
        var storageStream = CCIN("@mozilla.org/storagestream;1", "nsIStorageStream");
        var binaryOutputStream = CCIN("@mozilla.org/binaryoutputstream;1","nsIBinaryOutputStream");

        binaryInputStream.setInputStream(inputStream);
        storageStream.init(8192, count, null);
        binaryOutputStream.setOutputStream(storageStream.getOutputStream(0));

        // Copy received data as they come.
        var data = binaryInputStream.readBytes(count);
        this.receivedData.push(data);
        //alert(this.receivedData.toString());
        binaryOutputStream.writeBytes(data, count);

        this.originalListener.onDataAvailable(request, context,
            storageStream.newInputStream(0), offset, count);
    },
    
    onStopRequest: function(request, context, statusCode)
    {
        request.QueryInterface(Components.interfaces.nsIHttpChannel);
    	var requestURL = request.originalURI.prePath +""+request.originalURI.path;
    	var requestMtd = request.requestMethod.toLowerCase();
    	
      	if ( synchrona.enabled)
			{			
			    var txt = null;
				var postText = readPostTextFromRequest(request, context);
				if (postText)
				{
   		var str = parseURLEncodedText(postText);
					var msg = mapXhrPost( requestURL ,str);
					//alert(str);
					if(msg!=null)
					{
						try
						{
							dump("\n\nXHR MSG:\n"+msg);
							sendXMPP(msg);
						}
						catch (exmpp)
						{
						  alert("Error sending message over the network..");
						}
					}
					
				}
				else
				{
					//alert("Error in retrieving POST message");
				}
		} 
        // Get entire response
       //  alert(receivedData);
        var responseSource = this.receivedData.join();
        //alert(responseSource);
        this.originalListener.onStopRequest(request, context, statusCode);
       
    },
    


    QueryInterface: function (aIID) {
        if (aIID.equals(Components.interfaces.nsIStreamListener) || aIID.equals(Components.interfaces.nsISupports))
	{
            return this;
        }
        throw Components.results.NS_NOINTERFACE;
    }
}


function  readPostTextFromRequest(request, context) {
        try
        {
	        var is = request.QueryInterface(Components.interfaces.nsIUploadChannel).uploadStream;
	        if (is)
	        {
	            var ss = is.QueryInterface(Components.interfaces.nsISeekableStream);
	            var prevOffset;
	            if (ss)
	            {
	                prevOffset = ss.tell();
	                ss.seek(Components.interfaces.nsISeekableStream.NS_SEEK_SET, 0);
	            }

	            // Read data from the stream..
		   var charset = "UTF-8";
		   var text = readFromStream(is, charset, true);

	           if (ss && prevOffset == 0)
	               ss.seek(Components.interfaces.nsISeekableStream.NS_SEEK_SET, 0);
	           return text;	            
	        }
		else {
			//alert("Failed to Query Interface for upload stream.\n");
			//readPostTextFromPage(request, context);
		}
	    }
	    catch(exc)
	    {
			alert(exc.toString());
	    }

	    return null;
	}



	
function readFromStream(stream, charset, noClose){
		//fix for firebug error
		if (typeof Cc == "undefined") {
		var Cc = Components.classes;
		}
		if (typeof Ci == "undefined") {
        var Ci = Components.interfaces;
		}
		if (typeof CCIN == "undefined") {
		function CCIN(cName, ifaceName){
		return Cc[cName].createInstance(Ci[ifaceName]);
			}
		}
		if (typeof CCSV == "undefined") {
		function CCSV(cName, ifaceName){
			if (Cc[cName])
			// if fbs fails to load, the error can be _CC[cName] has no properties
			return Cc[cName].getService(Ci[ifaceName]);
			else
			dumpError("CCSV fails for cName:" + cName);
		}
		}
	    var sis = CCSV("@mozilla.org/binaryinputstream;1","nsIBinaryInputStream");
	    sis.setInputStream(stream);

	    var segments = [];
	    for (var count = stream.available(); count; count = stream.available())
	        segments.push(sis.readBytes(count));

	    if (!noClose)
	        sis.close();

	    var text = segments.join("");

try
    {
        return this.convertToUnicode(text, charset);
    }
    catch (err)
    {
//alert("covert error");
    }
	    return text;
	}

//parsing
function parseURLEncodedText(text)
{
    var maxValueLength = 25000;

    var params = [];

    // Unescape '+' characters that are used to encode a space.
    // See section 2.2.in RFC 3986: http://www.ietf.org/rfc/rfc3986.txt
    text = text.replace(/\+/g, " ");

    function decodeText(text)
    {
        try
        {
            return decodeURIComponent(text);
        }
        catch (e)
        {
            return decodeURIComponent(unescape(text));
        }
    }

    var args = text.split("&");
    for (var i = 0; i < args.length; ++i)
    {
        try
        {
            var index = args[i].indexOf("=");
            if (index != -1)
            {
                var paramName = args[i].substring(0, index);
                var paramValue = args[i].substring(index + 1);

                if (paramValue.length > maxValueLength )
                    paramValue = "DataTooLargeToParse";

                params.push({name: decodeText(paramName), value: decodeText(paramValue)});
            }
            else
            {
                var paramName = args[i];
                params.push({name: decodeText(paramName), value: ""});
            }
        }

        
        catch (e)
        {
        	alert(e.toString());
        }
    }

    params.sort(function(a, b) { return a.name <= b.name ? -1 : 1; });
 var str ="\n";
        
for(var k=0; k<params.length-1; k++)
{


str+= "<Element elementName=\""+params[k].name+"\">"+params[k].value+"</Element>"+"\n";

}

    return str;
}
